package com.frank.loadinglibrary.special.dot.anim;

import com.frank.loadinglibrary.special.dot.Config;
import com.frank.loadinglibrary.special.dot.CustomAnimatorStateListener;
import com.frank.loadinglibrary.special.dot.circle.BeadCircle;
import com.frank.loadinglibrary.special.dot.circle.WolfCircle;
import ohos.agp.animation.Animator;
import ohos.agp.animation.AnimatorValue;
import ohos.agp.components.Component;
import ohos.agp.render.Canvas;
import ohos.agp.render.Paint;
import ohos.agp.render.Path;

/**
 * @author SUQI
 * @date 2021/5/27
 * @description
 **/
public class SmallAndDropAnimator extends AnimatorValue {
    public final static int DURATION = Config.DURATION_DROP;
    private WolfCircle mCircle;
    private Component mView;
    // 水滴
    private BeadCircle mBead;
    private Path mPath;
    // 完整下落距离
    private float mDis;
    // 胶着的下落距离
    private float mixDis;

    AnimatorValue animatorValue;
    AnimatorValue animatorValue1;
    AnimatorValue animatorValue2;

    public SmallAndDropAnimator(Component view, WolfCircle circle) {
        mCircle = circle;
        mView = view;
        mixDis = circle.getRadius();
//        mDis = Config.CENTER_Y + Config.BIG_CIRCLE_RADIUS - Config.START_Y + mixDis;
        mDis = view.getHeight() - mixDis;
        Config.BASELINE = mDis;
        mBead = new BeadCircle(Config.START_X, Config.START_Y, 0);
        mPath = new Path();
        initAnim();
    }

    /**
     * 初始化动画的配置
     */
    public void initAnim() {
        this.setDuration(DURATION);
        // flatten distance 水滴放大的距离
        final float flattenDis = mixDis / 4;
        final float preFlattenDis = mixDis - flattenDis;
        // 由于要形成一个下落压缩的效果,所以在VALUE的设置上通过参数高->低->高->恢复这样的效果来实现
//        this.setIntValues(Config.START_Y, Config.START_Y + mixDis, mDis - preFlattenDis, mDis + flattenDis);
        this.setValueUpdateListener((animatorValue, v) -> {

        });
        setStateChangedListener(new CustomAnimatorStateListener() {
            @Override
            public void onStart(Animator animator) {
                animatorValue.start();
            }
        });
        animatorValue = new AnimatorValue();
        animatorValue.setDuration(DURATION / 3);
        animatorValue.setValueUpdateListener((animatorValue, v) -> {
            float curY = Config.START_Y + v * mixDis;
            falling(curY, preFlattenDis, flattenDis);
        });
        animatorValue.setStateChangedListener(new CustomAnimatorStateListener() {
            @Override
            public void onEnd(Animator animator) {
                animatorValue1.start();
            }
        });
        animatorValue1 = new AnimatorValue();
        animatorValue1.setDuration(DURATION / 3);
        animatorValue1.setValueUpdateListener((animatorValue, v) -> {
            float curY = Config.START_Y + mixDis - (Config.START_Y + mixDis - mDis + preFlattenDis) * v;
            falling(curY, preFlattenDis, flattenDis);
        });
        animatorValue1.setStateChangedListener(new CustomAnimatorStateListener() {
            @Override
            public void onEnd(Animator animator) {
                animatorValue2.start();
            }
        });
        animatorValue2 = new AnimatorValue();
        animatorValue2.setDuration(DURATION / 3);
        animatorValue2.setValueUpdateListener((animatorValue, v) -> {
            float curY = mDis - preFlattenDis + (flattenDis + preFlattenDis) * v;
            falling(curY, preFlattenDis, flattenDis);
        });
        animatorValue2.setStateChangedListener(new CustomAnimatorStateListener() {
            @Override
            public void onEnd(Animator animator) {
                mBead.reset(Config.START_X, Config.START_Y);
            }
        });
    }

    private void falling(float curY, float preFlattenDis, float flattenDis) {
        if (curY < mDis - preFlattenDis) {
            if (curY <= Config.START_Y + mixDis) {
                // 缩小
                mCircle.bigger(mixDis - curY + Config.START_Y);
                // 放大
                mBead.bigger(curY - Config.START_Y);
            }
            // 下落
            mBead.drop(curY);
        } else if (curY < mDis) {
            // 压缩
            mBead.flatten(mDis + flattenDis - curY);
            // 下落
            mBead.drop(curY);
        } else {
            // 压缩
            mBead.flatten(mDis + flattenDis - curY);
        }
        mView.invalidate();
    }

    public void draw(Canvas canvas, Paint paint) {
        mBead.draw(canvas, paint);
    }

    public BeadCircle getBead() {
        return mBead;
    }
}
